﻿using System.Collections.Generic;
using System.Xml.Linq;
using SharePointUtilitiesForDevelopers.Mapper;
using SharePointUtilitiesForDevelopers.Service;
using SharePointUtilitiesForDevelopers.WebsService;

namespace SharePointUtilitiesForDevelopers.Gateway
{
    /// <summary>
    /// Provides a gateway to the SharePoint Webs service.
    /// </summary>
    public class SharePointWebsServiceGateway : ISharePointWebsServiceGateway
    {
        /// <summary>
        /// Gets the site columns in the specified site.
        /// </summary>
        /// <typeparam name="TDomainObject">The type of the domain object.</typeparam>
        /// <param name="siteUrl">The site URL.</param>
        /// <param name="mapper">The mapper.</param>
        /// <returns>A list of <see cref="TDomainObject"/> objects.</returns>
        public IEnumerable<TDomainObject> GetSiteColumns<TDomainObject>(string siteUrl, IMapper<XElement, TDomainObject> mapper)
        {
            // Get the proxy
            var client = SharePointServiceClientFactory.CreateInstance<WebsSoapClient, WebsSoap>(siteUrl);

            // Get the response
            var response = XElement.Parse(client.GetColumns().OuterXml);

            // Return the mapped object
            return mapper.MapList(response);
        }

        /// <summary>
        /// Gets the specified content type.
        /// </summary>
        /// <typeparam name="TDomainObject">The type of the domain object.</typeparam>
        /// <param name="siteUrl">The site URL.</param>
        /// <param name="contentTypeId">The content type id.</param>
        /// <param name="mapper">The mapper.</param>
        /// <returns>A <see cref="TDomainObject"/>.</returns>
        public TDomainObject GetContentType<TDomainObject>(string siteUrl, string contentTypeId, IMapper<XElement, TDomainObject> mapper)
        {
            // Create the proxy
            var client = SharePointServiceClientFactory.CreateInstance<WebsSoapClient, WebsSoap>(siteUrl);

            // Get the response
            var response = XElement.Parse(client.GetContentType(contentTypeId).OuterXml);
            
            // Return the mapped object
            return mapper.Map(response);
        }
        
        /// <summary>
        /// Gets the content types.
        /// </summary>
        /// <typeparam name="TDomainObject">The type of the domain object.</typeparam>
        /// <param name="siteUrl">The site URL.</param>
        /// <param name="mapper">The mapper.</param>
        /// <returns>A list of <see cref="TDomainObject"/> objects.</returns>
        public IEnumerable<TDomainObject> GetContentTypes<TDomainObject>(string siteUrl, IMapper<XElement, TDomainObject> mapper)
        {
            // Create the proxy
            var client = SharePointServiceClientFactory.CreateInstance<WebsSoapClient, WebsSoap>(siteUrl);

            // Get the response
            var response = XElement.Parse(client.GetContentTypes().OuterXml);
            
            // Return the mapped object
            return mapper.MapList(response);
        }
        
        /// <summary>
        /// Gets the web.
        /// </summary>
        /// <typeparam name="TDomainObject">The type of the domain object.</typeparam>
        /// <param name="siteUrl">The site URL.</param>
        /// <param name="mapper">The mapper.</param>
        /// <returns>A <see cref="TDomainObject"/>.</returns>
        public TDomainObject GetWeb<TDomainObject>(string siteUrl, IMapper<XElement, TDomainObject> mapper)
        {
            // Create the proxy
            var client = SharePointServiceClientFactory.CreateInstance<WebsSoapClient, WebsSoap>(siteUrl);

            // Get the response
            var response = XElement.Parse(client.GetWeb(string.Empty).OuterXml);

            // Return the mapped object
            return mapper.Map(response);

        }
    }
}